package com.haixinga.commbiz.member.ctrl;

import cn.binarywang.wx.miniapp.api.WxMaService;
import cn.binarywang.wx.miniapp.api.impl.WxMaServiceImpl;
import cn.binarywang.wx.miniapp.bean.WxMaPhoneNumberInfo;
import cn.binarywang.wx.miniapp.bean.WxMaUserInfo;
import com.alibaba.fastjson.JSONObject;
import com.haixinga.commbiz.commons.biz.ITokenService;
import com.haixinga.commbiz.commons.entity.MemberAuth;
import com.haixinga.commbiz.commons.entity.MemberUser;
import com.haixinga.commbiz.commons.utils.RedisUtil;
import com.haixinga.commbiz.commons.vo.ApiRes;
import com.haixinga.commbiz.member.utils.MemberPropKit;
import com.haixinga.commbiz.commons.constants.CS;
import com.haixinga.commbiz.commons.exception.BizException;
import com.haixinga.commbiz.commons.service.MemberAuthService;
import com.haixinga.commbiz.commons.service.MemberUserService;
import com.haixinga.commbiz.commons.utils.AliyunSMSKit;
import com.haixinga.commbiz.commons.utils.JsonKit;
import com.haixinga.commbiz.commons.utils.StringKit;
import com.haixinga.commbiz.commons.vo.SMSConfigVO;
import com.haixinga.commbiz.member.vo.MemberLoginUserVO;
import org.apache.commons.lang3.StringUtils;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.web.bind.annotation.RequestMapping;
import org.springframework.web.bind.annotation.RequestMethod;
import org.springframework.web.bind.annotation.RestController;

import java.util.concurrent.TimeUnit;

/** 当前登录者的信息相关接口 **/
@RestController
@RequestMapping("api/current")
public class CurrentUserController extends CommonCtrl{

	@Autowired private MemberUserService memberUserService;
	@Autowired private MemberAuthService memberAuthService;


	/** 查询当前登录者用户信息 */
	@RequestMapping(value="/user", method = RequestMethod.GET)
	public ApiRes currentUserInfo() {

		MemberUser user = getCurrentUser().getMemberUser();
		return ApiRes.ok(user);
	}


	/** 重新绑定手机号码  + 根据用户数据信息 */
	@RequestMapping(value="bindTelphone", method = RequestMethod.POST)
	public ApiRes bindTelphone() throws BizException{

		MemberLoginUserVO currentUser = getCurrentUser();

		WxMaService wxService = new WxMaServiceImpl();

		// 解密用户信息
		WxMaUserInfo wxMaUserInfo = wxService.getUserService().getUserInfo(currentUser.getWxSessionKey(),
				getValStringRequired("userInfoEncData"), getValStringRequired("userInfoIv"));

		// 解密手机号
		WxMaPhoneNumberInfo phoneNoInfo = wxService.getUserService().getPhoneNoInfo(currentUser.getWxSessionKey(),
				getValStringRequired("telphoneEncData"), getValStringRequired("telphoneIv"));

		//获取微信解密数据
		String wxOpenId = wxMaUserInfo.getOpenId();
		String wxUnionId = wxMaUserInfo.getUnionId();
		String telPhone = phoneNoInfo.getPhoneNumber();

		if(StringUtils.isAnyEmpty(wxOpenId, wxUnionId, telPhone)){
			throw new BizException("获取用户信息有误!");
		}

		//查询手机号是否存在
		MemberUser findMemberUser = memberUserService.getOne(MemberUser.gw().eq(MemberUser::getTelphone, telPhone));
		if(findMemberUser != null){
			throw new BizException("当前手机号("+telPhone+")已绑定到用户["+findMemberUser.getRealname()+"]["+findMemberUser.getWxNickname()+"] !");
		}

		//查询微信小程序类型 + openId 是否已存在
		if(memberAuthService.count(MemberAuth.gw().eq(MemberAuth::getIdentityType, CS.AUTH_TYPE.WX_MINI).eq(MemberAuth::getIdentifier, wxOpenId)) > 0){
			throw new BizException("您已注册，请直接登录 !");
		}

		//转为为系统的微信用户数据VO
		MemberUser wxUserInfo = new MemberUser();
		wxUserInfo.setAvatarUrl(wxMaUserInfo.getAvatarUrl()); //头像地址
		wxUserInfo.setSex(Integer.parseInt(wxMaUserInfo.getGender()));  //性别
		wxUserInfo.setWxNickname(wxMaUserInfo.getNickName()); //昵称
		wxUserInfo.setWxAddressDesc(wxMaUserInfo.getCountry() + "-" + wxMaUserInfo.getProvince() + "-" +wxMaUserInfo.getCity()); //地区
		wxUserInfo.setTelphone(telPhone); //电话

		//插入用户数据
		Integer custUserId = 1; //memberUserService.checkAndAddMemberUser(wxUserInfo, CS.AUTH_TYPE.WX_MINI, wxOpenId, wxUnionId);
		MemberUser dbUser = memberUserService.getById(custUserId);

		//删除当前token的Redis缓存
		ITokenService.removeIToken(getCurrentUser().getIToken(), getCurrentUser().getUserId());

		//设置缓存对象信息
		MemberLoginUserVO loginUserVO = new MemberLoginUserVO();
		loginUserVO.setUserId(dbUser.getMuId());
		loginUserVO.setUsername(dbUser.getRealname());
		loginUserVO.setMemberUser(dbUser);

		loginUserVO.setWxOpenId(wxOpenId);
		loginUserVO.setWxUnionId(wxUnionId);
		loginUserVO.setWxSessionKey(currentUser.getWxSessionKey());

		//生成iToken 并放置到缓存
		String iToken = StringKit.getUUID();  //TODO 1 更改为更安全的方式
		ITokenService.processTokenCache(loginUserVO, iToken); //处理token 缓存信息

		JSONObject result = new JSONObject();
		result.put(CS.ACCESS_TOKEN_NAME, iToken);
		return ApiRes.ok(result);
	}

	/** 获取验证码  */
	@RequestMapping(value="smsCode", method = RequestMethod.GET)
	public ApiRes getSmsCode() throws BizException{

		String newTelphone = getValStringRequired("newTelphone");
		Integer time = 10;  //短信有效期, 单位分钟

		//发送短信
		SMSConfigVO smsConfigVO = MemberPropKit.getSMSConfig();
		String smsCode = AliyunSMSKit.genCode(smsConfigVO);

		boolean sendFlag = AliyunSMSKit.sendSMS(newTelphone, "SMS_179125271", JsonKit.newJson("code", smsCode), smsConfigVO);

		if(!sendFlag){ //发送失败
			throw new BizException("短信发送失败！");
		}

		//记录缓存
		RedisUtil.set(CS.getCacheKeyCustModifyMobile(getCurrentUser().getUserId(), newTelphone), smsCode, time, TimeUnit.MINUTES);
		return ApiRes.ok(JsonKit.newJson("time", time));
	}


	/** 修改手机号  */
	@RequestMapping(value="telphone", method = RequestMethod.PUT)
	public ApiRes updateTelphone() throws BizException{

		String newTelphone = getValStringRequired("newTelphone");
		String smsCode = getValStringRequired("smsCode");

		//保存的缓存记录
		String cacheCode = RedisUtil.getObject(CS.getCacheKeyCustModifyMobile(getCurrentUser().getUserId(), newTelphone), String.class);

		if(!smsCode.equalsIgnoreCase(cacheCode)){
			throw new BizException("短信验证码输入有误！");
		}

		MemberUser updateRecord = new MemberUser();
		updateRecord.setMuId(getCurrentUser().getUserId());
		updateRecord.setTelphone(newTelphone);
		memberUserService.updateById(updateRecord);

		//保存redis最新数据
		MemberLoginUserVO currentUser = getCurrentUser();
		currentUser.setMemberUser(memberUserService.getById(getCurrentUser().getUserId()));
		ITokenService.refData(currentUser);

		//删除短信验证码的缓存
		RedisUtil.del(CS.getCacheKeyCustModifyMobile(getCurrentUser().getUserId(), newTelphone));

		return ApiRes.ok();
	}


	/** 登出 */
	@RequestMapping(value="logout", method = RequestMethod.POST)
	public ApiRes logout() throws BizException{

		ITokenService.removeIToken(getCurrentUser().getIToken(), getCurrentUser().getUserId());
		return ApiRes.ok();
	}


}
